/*
	Compresor Gzip
    Copyright (C) 2012 Darío López Padial 
    @bukosabino

    This program is free software: you can redistribute it and/or modify
    it under the terms of the GNU General Public License as published by
    the Free Software Foundation, either version 3 of the License, or
    (at your option) any later version.

    This program is distributed in the hope that it will be useful,
    but WITHOUT ANY WARRANTY; without even the implied warranty of
    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
    GNU General Public License for more details.

    You should have received a copy of the GNU General Public License
    along with this program.  If not, see <http://www.gnu.org/licenses/>
*/

/**
 @file codificador.h
 @brief Especificación de la clase Codificador.
 @author Dario Lopez Padial
 */

#ifndef _Codificador_
#define _Codificador_

#include <iostream>
#include "vectorbits.h"

using namespace std;

/**
@struct Tabla
@brief Son los 3 campos de cada una de nuestras tablas.
*/
struct Tabla {
	unsigned int codigo;
	unsigned int num_bits;
	unsigned int lon_dis;
};


/**
@class Codificador
@brief Clase "puente" que usaremos para el algoritmo deflate de nuestro Gzip. Su función será codificar los
literales, distancias y longitudes encontradas por el algoritmo Lempel-Ziv en el flujo de entrada.
*/
class Codificador {

	private:

		Tabla tabla_distancia[31]; 
		Tabla tabla_lon_lit[30];
		Tabla tabla_huffman[4];

	public:

		/**
		@brief:	Constructor por defecto. Construye las tablas de Longitud, de Distancia y de codificación Huffman.
		*/
		Codificador ();

		/**
		@brief: Destructor. Destruye el objeto de la clase Codificador.
		*/
		~Codificador () {};

		/**
		@brief:				Se encarga de convertir el código de un literal o una longitud (codificada), en un vector
							de bits codificado según Huffman.
		@param codigo_aux:	Es el código que puede rondar entre 0 y 285, significará un literal o una longitud (codificada).
		@return:			Vector de bits codificado según Huffman, que corresponde con el código auxiliar de entrada.
		*/
		VB codigo_huffman ( unsigned int codigo_aux );

		/**
		@brief: 				Recibe un valor de longitud (originario de Lempel-Ziv) y lo codifica según la tabla de longitudes.
		@param longitud_aux: 	Valor de la longitud encontrada en en el algoritmo Lempel-Ziv.
		@param bits_auxiliares:	Devuelve por referencia el vector de bits auxiliar asociado a esa longitud.
		@return:				Devuelve el valor de la longitud codificada, y un vector de bits auxiliares asociado. 
		*/
		unsigned int longitud_codigo ( unsigned int longitud_aux, VB & bits_auxiliares );

		/**
		@brief:					Recibe un valor de distancia (originario de Lempel-Ziv) y lo codifica según la tabla de distancias.
		@param distancia_aux:	Es la distancia original del algoritmo Lempel-Ziv.
		@param bits_auxiliares:	Devuelve por referencia el vector de bits auxiliar asociado a esa distancia.
		@return:				La distancia codificada.
		*/
		unsigned int distancia_huffman ( unsigned int distancia_aux, VB & bits_auxiliares );

};

#endif
